package com.zcq.thumbup.job;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.text.StrPool;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.zcq.thumbup.mapper.BlogMapper;
import com.zcq.thumbup.model.entity.Thumb;
import com.zcq.thumbup.model.enums.ThumbTypeEnum;
import com.zcq.thumbup.service.ThumbService;
import com.zcq.thumbup.util.RedisKeyUtil;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

@Component
@Slf4j
public class SyncThumb2DBJob {

    @Resource
    private RedisTemplate<String, Object> redisTemplate;

    @Resource
    private ThumbService thumbService;

    @Resource
    private BlogMapper blogMapper;

    @Scheduled(fixedRate = 10000)
    @Transactional(rollbackFor = Exception.class)
    public void run() {
        log.info("开始执行");

        DateTime nowDate = DateUtil.date();
        // 如果秒数为0~9，则回到上一分钟的第50秒
        int second = (DateUtil.second(nowDate) / 10 - 1) * 10;
        if (second == -10) {
            second = 50;
            nowDate = DateUtil.offsetMinute(nowDate, -1);
        }
        String date = DateUtil.format(nowDate, "HH:mm:") + second;
        syncThumb2DBByDate(date);

        log.info("临时数据同步完成");
    }

    public void syncThumb2DBByDate(String date) {
        Map<Long, Long> blogThumbCountMap = new HashMap<>();

        // 获取临时点赞和取消点赞数据
        String tempThumbKey = RedisKeyUtil.getTempThumbKey(date);
        Map<Object, Object> allThumbMap = redisTemplate.opsForHash().entries(tempThumbKey);
        if (CollUtil.isEmpty(allThumbMap)) {
            return;
        }
        // Mysql新增/删除点赞数据
        List<Thumb> thumbList = new ArrayList<>();
        boolean needRemove = false;
        LambdaQueryWrapper<Thumb> objectLambdaQueryWrapper = new LambdaQueryWrapper<>();
        for (Object userIdBlogIdObj : allThumbMap.keySet()) {
            String userIdBlogId = String.valueOf(userIdBlogIdObj);
            String[] split = userIdBlogId.split(StrPool.COLON);
            Long userId = Long.valueOf(split[0]);
            Long blogId = Long.valueOf(split[1]);
            int thumbType = Integer.parseInt(String.valueOf(allThumbMap.get(userIdBlogIdObj)));

            if (ThumbTypeEnum.INCR.getValue() == thumbType) {
                Thumb thumb = new Thumb();
                thumb.setUserId(userId);
                thumb.setBlogId(blogId);
                thumbList.add(thumb);
            } else if (ThumbTypeEnum.DECR.getValue() == thumbType) {
                needRemove = true;
                objectLambdaQueryWrapper.or().eq(Thumb::getUserId, userId).eq(Thumb::getBlogId, blogId);
            } else {
                if (ThumbTypeEnum.NON.getValue() != thumbType) {
                    log.warn("数据异常：{}", userId + "," + blogId + "," + thumbType);
                }
                continue;
            }
            blogThumbCountMap.put(blogId, blogThumbCountMap.getOrDefault(blogId, 0L) + thumbType);
        }
        if (CollUtil.isNotEmpty(thumbList)) {
            thumbService.saveBatch(thumbList);
        }
        if (needRemove) {
            thumbService.remove(objectLambdaQueryWrapper);
        }
        // 更新博客的点赞数量
        if (CollUtil.isNotEmpty(blogThumbCountMap)) {
            blogMapper.batchUpdateThumbCount(blogThumbCountMap);
        }
        // 异步删除临时点赞和取消点赞数据
        Thread.startVirtualThread(() -> {
            redisTemplate.delete(tempThumbKey);
        });
    }

}
